﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.Data.OleDb;

namespace FlyShop
{
    public partial class FrmConsultaVoo : Form
    {
        // Indica o código do usuário logado
        public int codUsuario;
        // Nome do usuário
        public String nomeUsuario;
        //Nivel do usuário
        public Int32 nivel;
        //Variavel do logoff
        public bool logoff;
        public bool fechar;

        // Indica o código do registro selecionado no grid
        int indiceLinhaSelecionada;

        OleDbConnection conexao;
        OleDbCommand comando;
        OleDbDataAdapter da;
        DataSet ds;
        String strConexao = "Provider=MSDAORA.1;Data Source=localhost;Persist Security Info=True;User ID=pi;Password=pi";

        // Sql para consulta de todos os vôos cruzando os dados entre as relações
        String sqlConsulta = "select v.cod_voo, v.nome, v.valor, v.total_assentos, v.assentos_disponiveis, arnv.descricao as aerononave, v.data_partida, v.data_chegada, cp.nome as Cidade_Partida, cc.nome as Cidade_Chegada " +
            "from voo v, aeronave arnv, aeroporto ac, aeroporto ap, cidade cc, cidade cp where v.cod_aeronave = arnv.cod_aeronave and v.cod_aeroporto_chegada = ac.cod_aeroporto and v.cod_aeroporto_partida = ap.cod_aeroporto and ap.cod_cidade = cp.cod_cidade and ac.cod_cidade = cc.cod_cidade order by (case when data_partida <= sysdate then 'z' else 'a' end), data_partida";

        String sqlExcluiRegistro = "delete from voo where cod_voo = ?";

        String sqlConsultaFiltro = "select v.cod_voo, v.nome, v.valor, v.total_assentos, v.assentos_disponiveis, arnv.descricao as aerononave, v.data_partida, v.data_chegada, cp.nome as Cidade_Partida, cc.nome as Cidade_Chegada " +
           "from voo v, aeronave arnv, aeroporto ac, aeroporto ap, cidade cc, cidade cp where v.cod_aeronave = arnv.cod_aeronave and v.cod_aeroporto_chegada = ac.cod_aeroporto and v.cod_aeroporto_partida = ap.cod_aeroporto and ap.cod_cidade = cp.cod_cidade and ac.cod_cidade = cc.cod_cidade and v.nome like ? and cp.nome like ? and cc.nome like ? order by (case when data_partida <= sysdate then 'z' else 'a' end), data_partida";

        String sqlConsultaFiltroComAssentosDisponiveis = "select v.cod_voo, v.nome, v.valor, v.total_assentos, v.assentos_disponiveis, arnv.descricao as aerononave, v.data_partida, v.data_chegada, cp.nome as Cidade_Partida, cc.nome as Cidade_Chegada " +
           "from voo v, aeronave arnv, aeroporto ac, aeroporto ap, cidade cc, cidade cp where v.cod_aeronave = arnv.cod_aeronave and v.cod_aeroporto_chegada = ac.cod_aeroporto and v.cod_aeroporto_partida = ap.cod_aeroporto and ap.cod_cidade = cp.cod_cidade and ac.cod_cidade = cc.cod_cidade and v.nome like ? and cp.nome like ? and cc.nome like ? and assentos_disponiveis > 0 order by (case when data_partida <= sysdate then 'z' else 'a' end), data_partida";

        // Faz um menu para ver o relatório de ocupação em cima do datagridview com o botao direito
        ContextMenuStrip menu = new ContextMenuStrip();
        ToolStripMenuItem menuRelatorio = new ToolStripMenuItem("Relatório de Ocupação") { Image = FlyShop.Properties.Resources.ocupacao };


        public FrmConsultaVoo()
        {
            InitializeComponent();
        }

        public void atualiza()
        {
            // Faz uma consulta por todos os registros
            // Popula a grid
            da = new OleDbDataAdapter(sqlConsulta, conexao);
            ds = new DataSet();
            da.Fill(ds, "voo");
            dgvVoo.DataSource = ds.Tables["voo"];

            // Limpa a seleção e a variável de indicação do código
            dgvVoo.ClearSelection();
            indiceLinhaSelecionada = -1;

            // Limpa a label de mensagem e imagem de alerta
            lblMensagem.Text = "";
            alertNotificacao.Hide();

        }

        private void formataGrid()
        {
            dgvVoo.Columns[0].Visible = false;

            dgvVoo.Columns[1].HeaderText = "Nome";
            dgvVoo.Columns[1].AutoSizeMode = DataGridViewAutoSizeColumnMode.Fill;
            dgvVoo.Columns[2].HeaderText = "Valor";
            dgvVoo.Columns[2].Width = 70;
            dgvVoo.Columns[3].HeaderText = "Assentos";
            dgvVoo.Columns[3].Width = 65;
            dgvVoo.Columns[4].HeaderText = "Disponíveis";
            dgvVoo.Columns[4].Width = 80;
            dgvVoo.Columns[5].HeaderText = "Aeronave";
            dgvVoo.Columns[6].HeaderText = "Partida";
            dgvVoo.Columns[7].HeaderText = "Previsão";
            dgvVoo.Columns[8].HeaderText = "Origem";
            dgvVoo.Columns[8].Width = 140;
            dgvVoo.Columns[9].HeaderText = "Destino";
            dgvVoo.Columns[9].Width = 140;



            foreach (DataGridViewRow row in dgvVoo.Rows)
            {
                var now = DateTime.Now;
                var dataexpiracao = DateTime.Parse(row.Cells[6].Value.ToString());
                var embarque = dataexpiracao.AddHours(-5);

                if (now > embarque && now < dataexpiracao)
                {
                    row.DefaultCellStyle.BackColor = Color.LightBlue;
                }
                else if (now > dataexpiracao)
                {
                    row.DefaultCellStyle.BackColor = Color.Tomato;
                }
            }
        }

        private void btnCadastro_Load(object sender, EventArgs e)
        {

            lblUsuario.Text = "Colaborador: " + nomeUsuario;
            lblData.Text = DateTime.Now.ToLongDateString();
            fechar = false;
            
             /* Verifica o nível do usuário e bloqueia os componentes necessários
             * (usar apenas se for necessário)*/
            if (nivel ==  2)
            {
                aeronaveToolStripMenuItem.Enabled = false;
                usuárioToolStripMenuItem.Enabled = false;
                aeroportoToolStripMenuItem.Enabled = false;
            }
            

            try
            {
                // Estabelece conexão com o banco
                conexao = new OleDbConnection(strConexao);
                conexao.Open();
            }
            catch (Exception)
            {
                MessageBox.Show(this, "Não foi possível se conectar ao banco de dados.", "Conexão",
                    MessageBoxButtons.OK, MessageBoxIcon.Error);
                Application.Exit();
            }

            // Comando para configurar a sessão
            // Configura para o banco de dados ficar case-insensitive  
            OleDbCommand comandoAlteraSessao = new OleDbCommand("alter session set nls_sort=BINARY_CI", conexao);
            comandoAlteraSessao.ExecuteNonQuery();

            comandoAlteraSessao.CommandText = "alter session set nls_comp=LINGUISTIC";
            comandoAlteraSessao.ExecuteNonQuery();

            // Adiciona função ao botão de relatorio no datagridview
            menu.Items.AddRange(new ToolStripItem[] { menuRelatorio });
            menuRelatorio.Click += new EventHandler(menuRelatorio_Click);

            atualiza();
            formataGrid();
        }

        private void btnCadastrar_Click(object sender, EventArgs e)
        {
            FrmCadastroVoo frmCadastro = new FrmCadastroVoo();
            frmCadastro.Text = "Cadastro de voo";
            frmCadastro.ShowDialog();
            atualiza();
            formataGrid();
        }

        private void btnAlterar_Click(object sender, EventArgs e)
        {
            if (indiceLinhaSelecionada != -1)
            {
                FrmCadastroVoo frmEdicao = new FrmCadastroVoo();
                frmEdicao.Text = "Edição de voo";
                frmEdicao.edicao = true;
                frmEdicao.codVoo = Int32.Parse(dgvVoo.Rows[indiceLinhaSelecionada].Cells[0].Value.ToString());
                frmEdicao.ShowDialog();
                atualiza();
                formataGrid();
            }
            else
            {
                lblMensagem.Text = "Selecione um registro para alterar.";
                alertNotificacao.Show();
            }
        }

        private void btnExcluir_Click(object sender, EventArgs e)
        {
            if (indiceLinhaSelecionada != -1)
            {

                DialogResult drConfirmacao = MessageBox.Show(this, "Deseja excluir o registro selecionado?\nNão será possível excluir o registro caso ele tenha dependências.",
                  "Confirmação", MessageBoxButtons.YesNo, MessageBoxIcon.Question);

                if (drConfirmacao == DialogResult.Yes)
                {
                    comando = new OleDbCommand(sqlExcluiRegistro, conexao);

                    OleDbParameter pCod = new OleDbParameter("cod_voo", OleDbType.Integer);
                    pCod.Value = Int32.Parse(dgvVoo.Rows[indiceLinhaSelecionada].Cells[0].Value.ToString());
                    comando.Parameters.Add(pCod);

                    // Caso o registro em questão tenha dependentes
                    // será lançada uma exceção
                    try
                    {
                        // Delete
                        comando.ExecuteNonQuery();
                        atualiza();
                        formataGrid();
                    }
                    catch (OleDbException)
                    {
                        MessageBox.Show(this, "Não é possível excluir um registro com dependentes.",
                            "Operação inválida", MessageBoxButtons.OK, MessageBoxIcon.Warning);
                    }
                }

            }
            else
            {
                lblMensagem.Text = "Selecione um registro para excluir.";
                alertNotificacao.Show();
            }
        }

        private void dgvVoo_CellClick(object sender, DataGridViewCellEventArgs e)
        {
            indiceLinhaSelecionada = e.RowIndex;
        }



        private void cidadeToolStripMenuItem_Click(object sender, EventArgs e)
        {
            FrmConsultaCidade frmConCidade = new FrmConsultaCidade();
            frmConCidade.ShowDialog();
        }

        private void aeroportoToolStripMenuItem_Click(object sender, EventArgs e)
        {
            FrmConsultaAeroporto frmConAeroporto = new FrmConsultaAeroporto();
            frmConAeroporto.ShowDialog();
        }

        private void aeronaveToolStripMenuItem_Click(object sender, EventArgs e)
        {
            FrmConsultaAeronave frmConAeronave = new FrmConsultaAeronave();
            frmConAeronave.ShowDialog();
        }

        private void promocaoToolStripMenuItem_Click(object sender, EventArgs e)
        {
            FrmConsultaPromocao frmConPromo = new FrmConsultaPromocao();
            frmConPromo.ShowDialog();
        }

        private void Filtro_TextChanged(object sender, EventArgs e)
        {
            // Monta o comando para fazer a filtragem de voos
            comando = new OleDbCommand(sqlConsultaFiltro, conexao);

            OleDbParameter pNome = new OleDbParameter("nome", OleDbType.VarChar);
            pNome.Value = txtNome.Text.Trim() + "%";
            comando.Parameters.Add(pNome);

            OleDbParameter pCidadePartida = new OleDbParameter("cidade_partida", OleDbType.VarChar);
            pCidadePartida.Value = txtCidadeOrigem.Text.Trim() + "%";
            comando.Parameters.Add(pCidadePartida);

            OleDbParameter pCidadeChegada = new OleDbParameter("cidade_chegada", OleDbType.VarChar);
            pCidadeChegada.Value = txtCidadeDestino.Text.Trim() + "%";
            comando.Parameters.Add(pCidadeChegada);

            // Incrementa o comando de seleção
            if (ckbAssentosDisp.Checked)
            {
                comando.CommandText = sqlConsultaFiltroComAssentosDisponiveis;
            }

            da = new OleDbDataAdapter(comando);
            ds = new DataSet();
            da.Fill(ds, "voo");

            dgvVoo.DataSource = ds.Tables["voo"];

            dgvVoo.ClearSelection();
            indiceLinhaSelecionada = -1;

            // Atualiza as cores dos registros
            formataGrid();
        }

        private void dgvVoo_CellDoubleClick(object sender, DataGridViewCellEventArgs e)
        {
            if (indiceLinhaSelecionada != -1)
            {
                FrmCadastroVoo frmEdicao = new FrmCadastroVoo();
                frmEdicao.Text = "Edição de voo";
                frmEdicao.edicao = true;
                frmEdicao.codVoo = Int32.Parse(dgvVoo.Rows[indiceLinhaSelecionada].Cells[0].Value.ToString());
                frmEdicao.ShowDialog();
                atualiza();
                formataGrid();
            }
            else
            {
                lblMensagem.Text = "Selecione um registro para alterar.";
                alertNotificacao.Show();
            }
        }

        private void btnVender_Click(object sender, EventArgs e)
        {

            if (indiceLinhaSelecionada != -1)
            {

                String qntVoosDisponiveisTexto = dgvVoo.Rows[indiceLinhaSelecionada].Cells[4].Value.ToString();

                DateTime dtPartida = DateTime.Parse(dgvVoo.Rows[indiceLinhaSelecionada].Cells[6].Value.ToString());
                int rDatas = dtPartida.CompareTo(DateTime.Now);


                int qntVoosDisponiveis = Int32.Parse(qntVoosDisponiveisTexto);

                if (qntVoosDisponiveis <= 0)
                {
                    lblMensagem.Text = "Não há assentos disponíveis no voo selecionado.";
                    alertNotificacao.Show();
                }
                else if (rDatas <= 0)
                {   // retorno = 0 : mesma data
                    // retorno < 0 : data menor
                    lblMensagem.Text = "Não é possível vender a passagem de um voo que já partiu.";
                    alertNotificacao.Show();
                }
                else
                {
                    FrmRealizaVenda frmVenda = new FrmRealizaVenda();

                    int codVoo = Int32.Parse(dgvVoo.Rows[indiceLinhaSelecionada].Cells[0].Value.ToString());
                    String nomeVoo = dgvVoo.Rows[indiceLinhaSelecionada].Cells[1].Value.ToString();
                    String origem = dgvVoo.Rows[indiceLinhaSelecionada].Cells[8].Value.ToString();
                    String destino = dgvVoo.Rows[indiceLinhaSelecionada].Cells[9].Value.ToString();
                    String aeronave = dgvVoo.Rows[indiceLinhaSelecionada].Cells[5].Value.ToString();
                    String partida = dgvVoo.Rows[indiceLinhaSelecionada].Cells[6].Value.ToString();
                    String previsao = dgvVoo.Rows[indiceLinhaSelecionada].Cells[7].Value.ToString();
                    String nAssento = dgvVoo.Rows[indiceLinhaSelecionada].Cells[4].Value.ToString();
                    double valorVoo = Double.Parse(dgvVoo.Rows[indiceLinhaSelecionada].Cells[2].Value.ToString());
                    int totalAssentos = Int32.Parse(dgvVoo.Rows[indiceLinhaSelecionada].Cells[3].Value.ToString());

                    frmVenda.recebe(codUsuario, codVoo, nomeVoo, origem, destino, aeronave, partida, previsao, nAssento, valorVoo, totalAssentos);
                    frmVenda.ShowDialog();
                    atualiza();
                    formataGrid();
                }

            }
            else
            {
                lblMensagem.Text = "Selecione um voo para vender.";
                alertNotificacao.Show();
            }

        }

        private void dgvVoo_Sorted(object sender, EventArgs e)
        {
            // Limpa a seleção quando ordenar as linhas
            dgvVoo.ClearSelection();
            indiceLinhaSelecionada = -1;
            formataGrid();
        }

        private void clienteToolStripMenuItem_Click(object sender, EventArgs e)
        {
            FrmConsultaCliente frmConCliente = new FrmConsultaCliente();
            frmConCliente.ShowDialog();
        }

        private void usuárioToolStripMenuItem_Click(object sender, EventArgs e)
        {
            FrmConsultaUsuario frmConUsuario = new FrmConsultaUsuario();
            frmConUsuario.ShowDialog();
        }

        private void cancelarVendaToolStripMenuItem_Click(object sender, EventArgs e)
        {
            FrmCancelaVenda frmCanVenda = new FrmCancelaVenda();
            frmCanVenda.ShowDialog();
            atualiza();
            formataGrid();
        }

        private void menuRelatorio_Click(object sender, EventArgs e)
        {
            FrmRelatorioOcupacao frmOcupacao = new FrmRelatorioOcupacao();
            frmOcupacao.Text = "Relatório de Ocupação";
            frmOcupacao.codVoo = Int32.Parse(dgvVoo.Rows[indiceLinhaSelecionada].Cells[0].Value.ToString());
            frmOcupacao.ShowDialog();
            atualiza();
            formataGrid();
        }

        private void dgvVoo_MouseDown(object sender, MouseEventArgs e)
        {
            // verifica se o botão direito do mouse é pressionado dentro de um row atribuindo valor ao mesmo, caso seja pressionado fora não é executado o menu
            if (e.Button == MouseButtons.Right)
            {
                var ht = dgvVoo.HitTest(e.X, e.Y);
                indiceLinhaSelecionada = ht.RowIndex;

                if (ht.RowIndex != -1)
                {
                    dgvVoo.ContextMenuStrip = menu;
                    dgvVoo.Rows[ht.RowIndex].Selected = true;
                }
                else
                    dgvVoo.ContextMenuStrip = null;
            }
        }

        private void vendasToolStripMenuItem_Click(object sender, EventArgs e)
        {
            FrmRelatorioVendas frmRelatorioVendas = new FrmRelatorioVendas();
            frmRelatorioVendas.Text = "Relatório de Vendas";
            frmRelatorioVendas.ShowDialog();
            atualiza();
            formataGrid();
        }

        private void FrmConsultaVoo_FormClosing(object sender, FormClosingEventArgs e)
        {
            fechar = true;

            if (logoff == false && fechar == true)
            {
                if (MessageBox.Show("Deseja realmente sair?", "Sistema", MessageBoxButtons.YesNo, MessageBoxIcon.Question, MessageBoxDefaultButton.Button2) == DialogResult.No)
                {
                    e.Cancel = true;
                }
            }
           
        }

        private void FrmConsultaVoo_FormClosed(object sender, FormClosedEventArgs e)
        {
           if (logoff == false && fechar == true)
              Application.Exit();
        }

        private void sobreToolStripMenuItem_Click(object sender, EventArgs e)
        {
            FrmSobre frmSobreEmp = new FrmSobre();
            frmSobreEmp.ShowDialog();
        }

        private void logoutToolStripMenuItem_Click(object sender, EventArgs e)
        {
            if (MessageBox.Show("Deseja realmente fazer o logout?", "Atenção", MessageBoxButtons.YesNo, MessageBoxIcon.Exclamation) == DialogResult.Yes)
            {
                logoff = true;
                Close();
                FrmAutenticacao frmAutenticacao = new FrmAutenticacao();
                frmAutenticacao.ShowDialog();
            }

        }

        private void dgvVoo_CellEnter(object sender, DataGridViewCellEventArgs e)
        {
            indiceLinhaSelecionada = e.RowIndex;
        }

        private void FrmConsultaVoo_KeyDown(object sender, KeyEventArgs e)
        {
            //Hotkey para novo cadastro
            if (e.KeyData == (Keys.Control | Keys.N))
            {
                btnCadastrar_Click(sender, e);
            }
        }
    }
}
